/* * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You under the Apache License, Version 2.0 * (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package tests.api.javax.net.ssl; import java.io.IOException; import java.nio.ByteBuffer; import java.nio.ReadOnlyBufferException; import java.nio.channels.Pipe; import java.nio.channels.Pipe.SinkChannel; import java.nio.channels.Pipe.SourceChannel; import java.security.KeyManagementException; import java.security.NoSuchAlgorithmException; import java.util.Arrays; import java.util.HashSet; import java.util.Set; import javax.net.ssl.SSLContext; import javax.net.ssl.SSLEngine; import javax.net.ssl.SSLEngineResult; import javax.net.ssl.SSLException; import javax.net.ssl.SSLEngineResult.HandshakeStatus; import junit.framework.TestCase; import dalvik.annotation.AndroidOnly; import dalvik.annotation.KnownFailure; /** * Tests for SSLEngine class * */ public class SSLEngineTest extends TestCase { private HandshakeHandler clientEngine; private HandshakeHandler serverEngine; @Override protected void setUp() throws Exception { super.setUp(); } /** * Test for <code>SSLEngine()</code> constructor Assertion: creates * SSLEngine object with null host and -1 port * @throws NoSuchAlgorithmException */ public void test_Constructor() throws NoSuchAlgorithmException { SSLEngine e = getEngine(); assertNull(e.getPeerHost()); assertEquals(-1, e.getPeerPort()); String[] suites = e.getSupportedCipherSuites(); e.setEnabledCipherSuites(suites); assertEquals(e.getEnabledCipherSuites().length, suites.length); } /** * Test for <code>SSLEngine(String host, int port)</code> constructor * @throws NoSuchAlgorithmException */ public void test_ConstructorLjava_lang_StringI01() throws NoSuchAlgorithmException { int port = 1010; SSLEngine e = getEngine(null, port); assertNull(e.getPeerHost()); assertEquals(e.getPeerPort(), port); try { e.beginHandshake(); } catch (IllegalStateException ex) { // expected } catch (SSLException ex) { fail("unexpected SSLException was thrown."); } e = getEngine(null, port); e.setUseClientMode(true); try { e.beginHandshake(); } catch (SSLException ex) { // expected } e = getEngine(null, port); e.setUseClientMode(false); try { e.beginHandshake(); } catch (SSLException ex) { // expected } } /** * Test for <code>SSLEngine(String host, int port)</code> constructor * @throws NoSuchAlgorithmException */ public void test_ConstructorLjava_lang_StringI02() throws NoSuchAlgorithmException { String host = "new host"; int port = 8080; SSLEngine e = getEngine(host, port); assertEquals(e.getPeerHost(), host); assertEquals(e.getPeerPort(), port); String[] suites = e.getSupportedCipherSuites(); e.setEnabledCipherSuites(suites); assertEquals(e.getEnabledCipherSuites().length, suites.length); e.setUseClientMode(true); assertTrue(e.getUseClientMode()); } /** * Test for <code>getPeerHost()</code> method * @throws NoSuchAlgorithmException */ public void test_getPeerHost() throws NoSuchAlgorithmException { SSLEngine e = getEngine(); assertNull(e.getPeerHost()); e = getEngine("www.fortify.net", 80); assertEquals("Incorrect host name", "www.fortify.net", e.getPeerHost()); } /** * Test for <code>getPeerPort()</code> method * @throws NoSuchAlgorithmException */ public void test_getPeerPort() throws NoSuchAlgorithmException { SSLEngine e = getEngine(); assertEquals("Incorrect default value of peer port", -1 ,e.getPeerPort()); e = getEngine("www.fortify.net", 80); assertEquals("Incorrect peer port", 80, e.getPeerPort()); } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#getSupportedProtocols() */ public void test_getSupportedProtocols() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { String[] res = sse.getSupportedProtocols(); assertNotNull(res); assertTrue(res.length > 0); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#setEnabledProtocols(String[] protocols) * javax.net.ssl.SSLEngine#getEnabledProtocols() */ public void test_EnabledProtocols() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); String[] pr = sse.getSupportedProtocols(); try { sse.setEnabledProtocols(pr); String[] res = sse.getEnabledProtocols(); assertNotNull("Null array was returned", res); assertEquals("Incorrect array length", res.length, pr.length); assertTrue("Incorrect array was returned", Arrays.equals(res, pr)); } catch (Exception ex) { fail("Unexpected exception " + ex); } try { sse.setEnabledProtocols(null); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#getSupportedCipherSuites() */ public void test_getSupportedCipherSuites() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { String[] res = sse.getSupportedCipherSuites(); assertNotNull(res); assertTrue(res.length > 0); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#setEnabledCipherSuites(String[] suites) * javax.net.ssl.SSLEngine#getEnabledCipherSuites() */ public void test_EnabledCipherSuites() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); String[] st = sse.getSupportedCipherSuites(); try { sse.setEnabledCipherSuites(st); String[] res = sse.getEnabledCipherSuites(); assertNotNull("Null array was returned", res); assertEquals("Incorrect array length", res.length, st.length); assertTrue("Incorrect array was returned", Arrays.equals(res, st)); } catch (Exception ex) { fail("Unexpected exception " + ex); } try { sse.setEnabledCipherSuites(null); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#setEnableSessionCreation(boolean flag) * javax.net.ssl.SSLEngine#getEnableSessionCreation() */ public void test_EnableSessionCreation() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { assertTrue(sse.getEnableSessionCreation()); sse.setEnableSessionCreation(false); assertFalse(sse.getEnableSessionCreation()); sse.setEnableSessionCreation(true); assertTrue(sse.getEnableSessionCreation()); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#setNeedClientAuth(boolean need) * javax.net.ssl.SSLEngine#getNeedClientAuth() */ public void test_NeedClientAuth() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { sse.setNeedClientAuth(false); assertFalse(sse.getNeedClientAuth()); sse.setNeedClientAuth(true); assertTrue(sse.getNeedClientAuth()); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#setWantClientAuth(boolean want) * javax.net.ssl.SSLEngine#getWantClientAuth() */ public void test_WantClientAuth() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { sse.setWantClientAuth(false); assertFalse(sse.getWantClientAuth()); sse.setWantClientAuth(true); assertTrue(sse.getWantClientAuth()); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#beginHandshake() */ public void test_beginHandshake() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { sse.beginHandshake(); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException se) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } sse = getEngine("new host", 1080); try { sse.beginHandshake(); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException ise) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } sse = getEngine(); try { sse.setUseClientMode(true); sse.beginHandshake(); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#setUseClientMode(boolean mode) * javax.net.ssl.SSLEngine#getUseClientMode() */ @AndroidOnly("The RI doesn't throw the expected IllegalStateException.") public void test_UseClientMode() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { sse.setUseClientMode(false); assertFalse(sse.getUseClientMode()); sse.setUseClientMode(true); assertTrue(sse.getUseClientMode()); } catch (Exception ex) { fail("Unexpected exception " + ex); } try { sse = getEngine(null, 1080); sse.setUseClientMode(true); sse.beginHandshake(); try { sse.setUseClientMode(false); fail("IllegalArgumentException was not thrown"); } catch (IllegalArgumentException iae) { //expected } } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#getSession() */ public void test_getSession() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { assertNotNull(sse.getSession()); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#getHandshakeStatus() */ public void test_getHandshakeStatus() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { assertEquals(sse.getHandshakeStatus().toString(), "NOT_HANDSHAKING"); sse.setUseClientMode(true); sse.beginHandshake(); assertEquals(sse.getHandshakeStatus().toString(), "NEED_WRAP"); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#getDelegatedTask() */ @KnownFailure("com.android.org.conscrypt.SSLEngineImpl#getDelegatedTask() throws NPE instead of returning null") public void test_getDelegatedTask() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { assertNull(sse.getDelegatedTask()); } catch (Exception ex) { fail("Unexpected exception " + ex); } } /** * @throws IOException * @throws InterruptedException * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts, * int offset, int length) * Exception case: SSLException should be thrown. */ public void test_unwrap_01() throws IOException, InterruptedException { prepareEngines(); doHandshake(); ByteBuffer bbs = ByteBuffer.wrap(new byte[] {1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,3,1,2,31,2,3,1,2,3,1,2,3,1,2,3}); ByteBuffer bbd = ByteBuffer.allocate(100); try { clientEngine.engine.unwrap(bbs, new ByteBuffer[] { bbd }, 0, 1); fail("SSLException wasn't thrown"); } catch (SSLException ex) { //expected } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts, * int offset, int length) * Exception case: IndexOutOfBoundsException should be thrown. */ @KnownFailure("Fixed in DonutBurger, boundary checks missing") public void test_unwrap_02() throws SSLException { String host = "new host"; int port = 8080; ByteBuffer[] bbA = { ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; ByteBuffer bb = ByteBuffer.allocate(10); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bb, bbA, -1, 3); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } try { sse.unwrap(bb, bbA, 0, -3); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } try { sse.unwrap(bb, bbA, bbA.length + 1, bbA.length); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } try { sse.unwrap(bb, bbA, 0, bbA.length + 1); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts, * int offset, int length) * Exception case: ReadOnlyBufferException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_unwrap_03() { String host = "new host"; int port = 8080; ByteBuffer bbR = ByteBuffer.allocate(100).asReadOnlyBuffer(); ByteBuffer[] bbA = { bbR, ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; ByteBuffer bb = ByteBuffer.allocate(10); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bb, bbA, 0, bbA.length); fail("ReadOnlyBufferException wasn't thrown"); } catch (ReadOnlyBufferException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of ReadOnlyBufferException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts, * int offset, int length) * Exception case: IllegalArgumentException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_unwrap_04() { String host = "new host"; int port = 8080; ByteBuffer[] bbA = {ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100)}; ByteBuffer[] bbAN = {ByteBuffer.allocate(100), null, ByteBuffer.allocate(100)}; ByteBuffer[] bbN = null; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer bN = null; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bN, bbA, 0, 3); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bb, bbAN, 0, 3); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bb, bbN, 0, 0); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bN, bbN, 0, 0); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts, * int offset, int length) * Exception case: IllegalStateException should be thrown. */ @AndroidOnly("The RI doesn't throw the IllegalStateException.") public void test_unwrap_05() { String host = "new host"; int port = 8080; ByteBuffer[] bbA = { ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; ByteBuffer bb = ByteBuffer.allocate(10); SSLEngine sse = getEngine(host, port); try { sse.unwrap(bb, bbA, 0, bbA.length); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts, * int offset, int length) */ public void test_unwrap_06() { String host = "new host"; int port = 8080; ByteBuffer[] bbA = { ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; ByteBuffer bb = ByteBuffer.allocate(10); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { SSLEngineResult res = sse.unwrap(bb, bbA, 0, bbA.length); assertEquals(0, res.bytesConsumed()); assertEquals(0, res.bytesProduced()); } catch (Exception ex) { fail("Unexpected exception: " + ex); } } public void test_wrap_01() throws IOException, InterruptedException { prepareEngines(); doHandshake(); ByteBuffer bbs = ByteBuffer.allocate(100); ByteBuffer bbd = ByteBuffer.allocate(20000); clientEngine.engine.wrap(new ByteBuffer[] { bbs }, 0, 1, bbd); } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, int offset, * int length, ByteBuffer dst) * Exception case: IndexOutOfBoundsException should be thrown. */ @KnownFailure("Fixed in DonutBurger, boundary checks missing") public void test_wrap_02() throws SSLException { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer[] bbA = {ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5)}; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbA, -1, 3, bb); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } try { sse.wrap(bbA, 0, -3, bb); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } try { sse.wrap(bbA, bbA.length + 1, bbA.length, bb); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } try { sse.wrap(bbA, 0, bbA.length + 1, bb); fail("IndexOutOfBoundsException wasn't thrown"); } catch (IndexOutOfBoundsException iobe) { //expected } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, int offset, * int length, ByteBuffer dst) * Exception case: ReadOnlyBufferException should be thrown. */ public void test_wrap_03() throws SSLException { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10).asReadOnlyBuffer(); ByteBuffer[] bbA = {ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5)}; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbA, 0, bbA.length, bb); fail("ReadOnlyBufferException wasn't thrown"); } catch (ReadOnlyBufferException iobe) { //expected } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, int offset, * int length, ByteBuffer dst) * Exception case: IllegalArgumentException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_wrap_04() { String host = "new host"; int port = 8080; ByteBuffer[] bbA = {ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100)}; ByteBuffer[] bbN = null; ByteBuffer bN = null; SSLEngine e = getEngine(host, port); e.setUseClientMode(true); try { e.wrap(bbA, 0, 3, bN); fail("IllegalArgumentException must be thrown for null srcs byte buffer array"); } catch (NullPointerException npe) { } catch (IllegalArgumentException ex) { } catch (Exception ex) { fail(ex + " was thrown instead of IllegalArgumentException"); } try { e.wrap(bbN, 0, 0, bN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException ex) { } catch (NullPointerException npe) { } catch (Exception ex) { fail(ex + " was thrown instead of IllegalArgumentException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, int offset, * int length, ByteBuffer dst) * Exception case: IllegalStateException should be thrown. */ @AndroidOnly("The RI doesn't throw the IllegalStateException.") public void test_wrap_05() throws SSLException { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer[] bbA = {ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5)}; SSLEngine sse = getEngine(host, port); try { sse.wrap(bbA, 0, bbA.length, bb); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException iobe) { //expected } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, int offset, * int length, ByteBuffer dst) */ public void test_wrap_06() { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer[] bbA = {ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5)}; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbA, 0, bbA.length, bb); } catch (Exception ex) { fail("Unexpected exception: " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#closeOutbound() * javax.net.ssl.SSLEngine#isOutboundDone() */ public void test_closeOutbound() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { assertFalse(sse.isOutboundDone()); sse.closeOutbound(); assertTrue(sse.isOutboundDone()); } catch (Exception ex) { fail("Unexpected exception: " + ex); } } /** * @throws NoSuchAlgorithmException * javax.net.ssl.SSLEngine#closeInbound() * javax.net.ssl.SSLEngine#isInboundDone() */ public void test_closeInbound() throws NoSuchAlgorithmException { SSLEngine sse = getEngine(); try { assertFalse(sse.isInboundDone()); sse.closeInbound(); assertTrue(sse.isInboundDone()); } catch (Exception ex) { fail("Unexpected exception: " + ex); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer dst) * SSLException should be thrown. */ public void test_unwrap_ByteBuffer_ByteBuffer_01() throws InterruptedException, IOException { prepareEngines(); doHandshake(); ByteBuffer bbs = ByteBuffer.allocate(100); ByteBuffer bbd = ByteBuffer.allocate(100); try { SSLEngineResult unwrap = clientEngine.engine.unwrap(bbs, bbd); fail("SSLException wasn't thrown"); } catch (SSLException ex) { //expected } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer dst) * ReadOnlyBufferException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_unwrap_ByteBuffer_ByteBuffer_02() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(100).asReadOnlyBuffer(); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bbs, bbd); fail("ReadOnlyBufferException wasn't thrown"); } catch (ReadOnlyBufferException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of ReadOnlyBufferException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer dst) * IllegalArgumentException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_unwrap_ByteBuffer_ByteBuffer_03() { String host = "new host"; int port = 8080; ByteBuffer bbsN = null; ByteBuffer bbdN = null; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(100); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bbsN, bbd); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bbs, bbdN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bbsN, bbdN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer dst) * IllegalStateException should be thrown. */ @AndroidOnly("The RI doesn't throw the IllegalStateException.") public void test_unwrap_ByteBuffer_ByteBuffer_04() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(100); SSLEngine sse = getEngine(host, port); try { sse.unwrap(bbs, bbd); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer dst) */ public void test_unwrap_ByteBuffer_ByteBuffer_05() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(100); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { SSLEngineResult res = sse.unwrap(bbs, bbd); assertEquals(0, res.bytesConsumed()); assertEquals(0, res.bytesProduced()); } catch (Exception e) { fail("Unexpected exception: " + e); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts) * SSLException should be thrown. */ public void test_unwrap_ByteBuffer$ByteBuffer_01() throws IOException, InterruptedException { prepareEngines(); doHandshake(); ByteBuffer bbs = ByteBuffer.allocate(100); ByteBuffer bbd = ByteBuffer.allocate(100); try { clientEngine.engine.unwrap(bbs, new ByteBuffer[] { bbd }); fail("SSLException wasn't thrown"); } catch (SSLException ex) { //expected } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts) * ReadOnlyBufferException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_unwrap_ByteBuffer$ByteBuffer_02() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbR = ByteBuffer.allocate(100).asReadOnlyBuffer(); ByteBuffer[] bbA = { bbR, ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bbs, bbA); fail("ReadOnlyBufferException wasn't thrown"); } catch (ReadOnlyBufferException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of ReadOnlyBufferException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts) * IllegalArgumentException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_unwrap_ByteBuffer$ByteBuffer_03() { String host = "new host"; int port = 8080; ByteBuffer[] bbA = { ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; ByteBuffer[] bbN = { ByteBuffer.allocate(100), null, ByteBuffer.allocate(100) }; ByteBuffer[] bbAN = null; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer bN = null; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.unwrap(bN, bbA); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bb, bbAN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bb, bbN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.unwrap(bN, bbAN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts) * IllegalStateException should be thrown. */ @AndroidOnly("The RI doesn't throw the IllegalStateException.") public void test_unwrap_ByteBuffer$ByteBuffer_04() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer[] bbd = {ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; SSLEngine sse = getEngine(host, port); try { sse.unwrap(bbs, bbd); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } } /** * javax.net.ssl.SSLEngine#unwrap(ByteBuffer src, ByteBuffer[] dsts) */ public void test_unwrap_ByteBuffer$ByteBuffer_05() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer[] bbd = {ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100) }; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { SSLEngineResult res = sse.unwrap(bbs, bbd); assertEquals(0, res.bytesConsumed()); assertEquals(0, res.bytesProduced()); } catch (Exception ex) { fail("Unexpected exception: " + ex); } } public void test_wrap_ByteBuffer_ByteBuffer_01() throws IOException, InterruptedException { prepareEngines(); doHandshake(); ByteBuffer bbs = ByteBuffer.allocate(20); ByteBuffer bbd = ByteBuffer.allocate(20000); clientEngine.engine.wrap(bbs, bbd); } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer src, ByteBuffer dst) * ReadOnlyBufferException should be thrown. */ public void test_wrap_ByteBuffer_ByteBuffer_02() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(100).asReadOnlyBuffer(); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbs, bbd); fail("ReadOnlyBufferException wasn't thrown"); } catch (ReadOnlyBufferException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of ReadOnlyBufferException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer src, ByteBuffer dst) * IllegalArgumentException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_wrap_ByteBuffer_ByteBuffer_03() { String host = "new host"; int port = 8080; ByteBuffer bbsN = null; ByteBuffer bbdN = null; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(100); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbsN, bbd); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.wrap(bbs, bbdN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.wrap(bbsN, bbdN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iae) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer src, ByteBuffer dst) * IllegalStateException should be thrown. */ @AndroidOnly("The RI doesn't throw the IllegalStateException.") public void test_wrap_ByteBuffer_ByteBuffer_04() { String host = "new host"; int port = 8080; ByteBuffer bbs = ByteBuffer.allocate(10); ByteBuffer bbd = ByteBuffer.allocate(10); SSLEngine sse = getEngine(host, port); try { sse.wrap(bbs, bbd); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer src, ByteBuffer dst) */ public void test_wrap_ByteBuffer_ByteBuffer_05() { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10); SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { SSLEngineResult res = sse.wrap(bb, ByteBuffer.allocate(10)); assertEquals(0, res.bytesConsumed()); assertEquals(0, res.bytesProduced()); } catch (Exception e) { fail("Unexpected exception: " + e); } } /** * @throws IOException * @throws InterruptedException * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, ByteBuffer dst) * SSLException should be thrown. */ public void test_wrap_ByteBuffer$ByteBuffer_01() throws IOException, InterruptedException { prepareEngines(); doHandshake(); ByteBuffer bbs = ByteBuffer.allocate(100); ByteBuffer bbd = ByteBuffer.allocate(20000); try { clientEngine.engine.wrap(new ByteBuffer[] { bbs }, bbd); serverEngine.engine.wrap(new ByteBuffer[] { bbs }, bbd); //fail("SSLException wasn't thrown"); } catch (SSLException ex) { //expected } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, ByteBuffer dst) * ReadOnlyBufferException should be thrown. */ public void test_wrap_ByteBuffer$ByteBuffer_02() { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10).asReadOnlyBuffer(); ByteBuffer[] bbA = {ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5)}; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbA, bb); fail("ReadOnlyBufferException wasn't thrown"); } catch (ReadOnlyBufferException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of ReadOnlyBufferException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, ByteBuffer dst) * IllegalArgumentException should be thrown. */ @KnownFailure("Fixed on DonutBurger, Wrong Exception thrown") public void test_wrap_ByteBuffer$ByteBuffer_03() { String host = "new host"; int port = 8080; ByteBuffer[] bbA = {ByteBuffer.allocate(100), ByteBuffer.allocate(10), ByteBuffer.allocate(100)}; ByteBuffer[] bbAN = null; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer bN = null; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { sse.wrap(bbA, bN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.wrap(bbAN, bb); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } try { sse.wrap(bbAN, bN); fail("IllegalArgumentException wasn't thrown"); } catch (IllegalArgumentException iobe) { //expected } catch (NullPointerException npe) { } catch (Exception e) { fail(e + " was thrown instead of IllegalArgumentException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, ByteBuffer dst) * IllegalStateException should be thrown. */ @AndroidOnly("The RI doesn't throw the IllegalStateException.") public void test_wrap_ByteBuffer$ByteBuffer_04() { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer[] bbA = { ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5) }; SSLEngine sse = getEngine(host, port); try { sse.wrap(bbA, bb); fail("IllegalStateException wasn't thrown"); } catch (IllegalStateException iobe) { //expected } catch (Exception e) { fail(e + " was thrown instead of IllegalStateException"); } } /** * javax.net.ssl.SSLEngine#wrap(ByteBuffer[] srcs, ByteBuffer dst) */ public void test_wrap_ByteBuffer$ByteBuffer_05() { String host = "new host"; int port = 8080; ByteBuffer bb = ByteBuffer.allocate(10); ByteBuffer[] bbA = { ByteBuffer.allocate(5), ByteBuffer.allocate(10), ByteBuffer.allocate(5) }; SSLEngine sse = getEngine(host, port); sse.setUseClientMode(true); try { SSLEngineResult res = sse.wrap(bbA, bb); assertEquals(0, res.bytesConsumed()); assertEquals(0, res.bytesProduced()); } catch (Exception ex) { fail("Unexpected exception: " + ex); } } private SSLEngine getEngine() { SSLContext context = null; try { context = SSLContext.getInstance("TLS"); context.init(null, null, null); } catch (KeyManagementException e) { fail("Could not get SSLEngine: key management exception " + e.getMessage()); } catch (NoSuchAlgorithmException e) { fail("Could not get SSLEngine: no such algorithm " + e.getMessage()); } return context.createSSLEngine(); } private SSLEngine getEngine(String host, int port) { SSLContext context = null; try { context = SSLContext.getInstance("TLS"); context.init(null, null, null); } catch (KeyManagementException e) { fail("Could not get SSLEngine: key management exception " + e.getMessage()); } catch (NoSuchAlgorithmException e) { fail("Could not get SSLEngine: no such algorithm " + e.getMessage()); } return context.createSSLEngine(host, port); } class HandshakeHandler implements Runnable { private final SSLEngine engine; private final SourceChannel in; private final SinkChannel out; private final ByteBuffer EMPTY = ByteBuffer.allocate(0); @SuppressWarnings("unused") private final String LOGTAG; private SSLEngineResult.HandshakeStatus status; private ByteBuffer readBuffer; private ByteBuffer writeBuffer; HandshakeHandler(boolean clientMode, SourceChannel in, SinkChannel out) throws SSLException { this.in = in; this.out = out; engine = getEngine(); engine.setUseClientMode(clientMode); String[] cipherSuites = engine.getSupportedCipherSuites(); Set<String> enabledSuites = new HashSet<String>(); for (String cipherSuite : cipherSuites) { if (cipherSuite.contains("anon")) { enabledSuites.add(cipherSuite); } } engine.setEnabledCipherSuites((String[]) enabledSuites.toArray( new String[enabledSuites.size()])); engine.beginHandshake(); status = engine.getHandshakeStatus(); if (clientMode) { LOGTAG = "CLIENT: "; } else { LOGTAG = "SERVER: "; } log("CipherSuites: " + Arrays.toString(engine.getEnabledCipherSuites())); log(status); readBuffer = ByteBuffer.allocate(200000); writeBuffer = ByteBuffer.allocate(20000); } public SSLEngineResult.HandshakeStatus getStatus() { return status; } private void log(Object o) { //System.out.print(LOGTAG); //System.out.println(o); } private ByteBuffer read() throws IOException { if (readBuffer == null || readBuffer.remaining() == 0 || readBuffer.position() == 0) { readBuffer.clear(); int read = in.read(readBuffer); log("read: " + read); readBuffer.rewind(); readBuffer.limit(read); } return readBuffer; } public void run() { try { while (true) { switch (status) { case FINISHED: { log(status); return; } case NEED_TASK: { log(status); Runnable task; while ((task = engine.getDelegatedTask()) != null) { task.run(); } status = engine.getHandshakeStatus(); break; } case NEED_UNWRAP: { log(status); ByteBuffer source = read(); writeBuffer.clear(); while (status == HandshakeStatus.NEED_UNWRAP) { SSLEngineResult result = engine.unwrap(source, writeBuffer); status = result.getHandshakeStatus(); log(result); } break; } case NEED_WRAP: { log(status); writeBuffer.clear(); int produced = 0; SSLEngineResult result = null; while (status == HandshakeStatus.NEED_WRAP) { result = engine.wrap(EMPTY, writeBuffer); status = result.getHandshakeStatus(); produced += result.bytesProduced(); log(result); } writeBuffer.rewind(); writeBuffer.limit(produced); log("write: " + produced); out.write(writeBuffer); break; } case NOT_HANDSHAKING: { log("Not Handshaking"); return; } } } } catch (IOException e) { log(e); } catch (RuntimeException e) { // ignore; } } } @KnownFailure("Handshake Status is never finished. NPE in " + "ClientSessionContext$HostAndPort.hashCode() when host is null") public void testHandshake() throws IOException, InterruptedException { prepareEngines(); assertTrue("handshake failed", doHandshake()); System.out.println(clientEngine.engine.getSession().getCipherSuite()); assertEquals("Handshake not finished", SSLEngineResult.HandshakeStatus.FINISHED, clientEngine.getStatus()); assertEquals("Handshake not finished", SSLEngineResult.HandshakeStatus.FINISHED, serverEngine.getStatus()); } void prepareEngines() throws IOException { Pipe clientSendPipe = Pipe.open(); Pipe serverSendPipe = Pipe.open(); SinkChannel clientSink = clientSendPipe.sink(); SourceChannel serverSource = clientSendPipe.source(); SinkChannel serverSink = serverSendPipe.sink(); SourceChannel clientSource = serverSendPipe.source(); clientEngine = new HandshakeHandler(true, clientSource, clientSink); serverEngine = new HandshakeHandler(false, serverSource, serverSink); } boolean doHandshake() throws InterruptedException { Thread clientThread = new Thread(clientEngine); clientThread.start(); Thread serverThread = new Thread(serverEngine); serverThread.start(); int i = 0; while (clientThread.isAlive() && serverThread.isAlive() && i < 20) { Thread.sleep(500); i++; } if (clientThread.isAlive()) { clientThread.interrupt(); } if (serverThread.isAlive()) { serverThread.interrupt(); } return clientEngine.getStatus() == HandshakeStatus.FINISHED && serverEngine.getStatus() == HandshakeStatus.FINISHED; } }